package br.mikhas.container.factory.processor;

import br.mikhas.container.config.BeanDefinition;
import br.mikhas.container.factory.BeanFactory;
import br.mikhas.container.factory.BeanPostProcessor;
import br.mikhas.container.factory.InitializingBeanFactory;

/**
 * Registers on the defined {@link BeanFactory} resources which implements
 * {@link BeanPostProcessor} interface.
 * 
 * @author Mikhail Domanoski
 * 
 */
public class PostProcessorRegisterPostProcessor implements BeanPostProcessor {

	private InitializingBeanFactory beanFactory;

	/**
	 * To process the resource, this {@link BeanPostProcessor} must contains an
	 * instance of {@link InitializingBeanFactory} and the resource must be
	 * instance of {@link BeanPostProcessor}.
	 */
	@Override
	public boolean mayProcess(BeanDefinition definition) {
		if (beanFactory != null) {
			Class<?> resourceType = definition.getType();
			return BeanPostProcessor.class.isAssignableFrom(resourceType);
		} else
			return false;
	}

	/**
	 * Register the {@link BeanPostProcessor} on the current {@link BeanFactory}
	 * .
	 */
	@Override
	public Object processBean(BeanDefinition definition, Object resource) {
		BeanPostProcessor rpp = (BeanPostProcessor) resource;
		beanFactory.registerResourcePostProcessor(rpp);
		return resource;
	}

	/**
	 * Sets the {@link BeanFactory} only if it's instance of
	 * {@link InitializingBeanFactory}.
	 */
	@Override
	public void setBeanFactory(BeanFactory beanFactory) {
		if (beanFactory.getClass().isAssignableFrom(
				InitializingBeanFactory.class)) {
			this.beanFactory = (InitializingBeanFactory) beanFactory;
		}
	}

}
